
package com.hockeo.tinygds;

import java.lang.reflect.Field;

import com.hockeo.tinygds.error.TNotLoadableException;

/**
 *
 * @version $Id$
 * @author jjanke
 */
public class TFieldNumber extends TField<Number>
{
  protected TFieldNumber( TinyGDSFactory factory, Field field )
  {
    super( factory, field );
  }

  @Override
  protected boolean isDirectlySettable( Object objDatastoreValue )
  {
    // for numbers, only null values are directly assignable - everything else must be converted
    //
    if ( objDatastoreValue == null )
      return true;

    return false;
  }

  @Override
  protected Number transformDatastoreValue( Object objDatastoreValue )
  {
    if ( objDatastoreValue instanceof Number )
      return transformNumber( (Number) objDatastoreValue );

    throw TNotLoadableException.cannotConvertValue( objDatastoreValue, getRealField() );
  }

  /**
   * Transforms the numeric value into a value of the specified type. This is necessary as
   * the datastore stores all numbers as Long.
   *
   * @param value the value to transform
   * @return the transformed number
   */
  private Number transformNumber( Number value )
  {
    Class<?> clsType = getRealField().getType();

    if ( ( clsType == Byte.class ) || ( clsType == Byte.TYPE ) )
      return value.byteValue();
    else if ( ( clsType == Short.class ) || ( clsType == Short.TYPE ) )
      return value.shortValue();
    else if ( ( clsType == Integer.class ) || ( clsType == Integer.TYPE ) )
      return value.intValue();
    else if ( ( clsType == Long.class ) || ( clsType == Long.TYPE ) )
      return value.longValue();
    else if ( ( clsType == Float.class ) || ( clsType == Float.TYPE ) )
      return value.floatValue();
    else if ( ( clsType == Double.class ) || ( clsType == Double.TYPE ) )
      return value.doubleValue();
    else
      throw TNotLoadableException.cannotConvertValue( value, getRealField() );
  }
}
